home *** CD-ROM | disk | FTP | other *** search
/ QRZ! Ham Radio 8 / QRZ Ham Radio Callsign Database - Volume 8.iso / mac / files / t_sys5 / 92052tar.gz / 920528.tar / tcpcmd.c < prev    next >
C/C++ Source or Header  |  1992-05-14  |  7KB  |  319 lines

  1. /* @(#) $Header: tcpcmd.c,v 1.8 92/05/14 13:20:31 deyke Exp $ */
  2.  
  3. /* TCP control and status routines
  4.  * Copyright 1991 Phil Karn, KA9Q
  5.  */
  6. #include <stdio.h>
  7. #include "global.h"
  8. #include "timer.h"
  9. #include "mbuf.h"
  10. #include "netuser.h"
  11. #include "internet.h"
  12. #include "tcp.h"
  13. #include "cmdparse.h"
  14. #include "commands.h"
  15.  
  16. static int doirtt __ARGS((int argc,char *argv[],void *p));
  17. static int domss __ARGS((int argc,char *argv[],void *p));
  18. static int dortt __ARGS((int argc,char *argv[],void *p));
  19. static int dotcpkick __ARGS((int argc,char *argv[],void *p));
  20. static int dotcpreset __ARGS((int argc,char *argv[],void *p));
  21. static int dotcpstat __ARGS((int argc,char *argv[],void *p));
  22. static int dotcptr __ARGS((int argc,char *argv[],void *p));
  23. static int dowindow __ARGS((int argc,char *argv[],void *p));
  24. static int dosyndata __ARGS((int argc,char *argv[],void *p));
  25. static int tstat __ARGS((void));
  26.  
  27. /* TCP subcommand table */
  28. static struct cmds Tcpcmds[] = {
  29.     "irtt",         doirtt,         0, 0,   NULLCHAR,
  30.     "kick",         dotcpkick,      0, 2,   "tcp kick <tcb>",
  31.     "mss",          domss,          0, 0,   NULLCHAR,
  32.     "reset",        dotcpreset,     0, 2,   "tcp reset <tcb>",
  33.     "rtt",          dortt,          0, 3,   "tcp rtt <tcb> <val>",
  34.     "status",       dotcpstat,      0, 0,   NULLCHAR,
  35.     "syndata",      dosyndata,      0, 0,   NULLCHAR,
  36.     "trace",        dotcptr,        0, 0,   NULLCHAR,
  37.     "window",       dowindow,       0, 0,   NULLCHAR,
  38.     NULLCHAR,
  39. };
  40. int
  41. dotcp(argc,argv,p)
  42. int argc;
  43. char *argv[];
  44. void *p;
  45. {
  46.     return subcmd(Tcpcmds,argc,argv,p);
  47. }
  48. static int
  49. dotcptr(argc,argv,p)
  50. int argc;
  51. char *argv[];
  52. void *p;
  53. {
  54.     return setbool(&Tcp_trace,"TCP state tracing",argc,argv);
  55. }
  56.  
  57. /* Eliminate a TCP connection */
  58. static int
  59. dotcpreset(argc,argv,p)
  60. int argc;
  61. char *argv[];
  62. void *p;
  63. {
  64.     register struct tcb *tcb;
  65.  
  66.     tcb = (struct tcb *)ltop(htol(argv[1]));
  67.     if(!tcpval(tcb)){
  68.         printf(Notval);
  69.         return 1;
  70.     }
  71.     reset_tcp(tcb);
  72.     return 0;
  73. }
  74.  
  75. /* Set initial round trip time for new connections */
  76. static int
  77. doirtt(argc,argv,p)
  78. int argc;
  79. char *argv[];
  80. void *p;
  81. {
  82.     struct tcp_rtt *tp;
  83.  
  84.     setlong(&Tcp_irtt,"TCP default irtt",argc,argv);
  85.     if(argc < 2){
  86.         for(tp = &Tcp_rtt[0];tp < &Tcp_rtt[RTTCACHE];tp++){
  87.             if(tp->addr != 0){
  88.                 if(printf("%s: srtt %lu mdev %lu\n",
  89.                  inet_ntoa(tp->addr),
  90.                  tp->srtt,tp->mdev) == EOF)
  91.                     break;
  92.             }
  93.         }
  94.     }
  95.     return 0;
  96. }
  97.  
  98. /* Set smoothed round trip time for specified TCB */
  99. static int
  100. dortt(argc,argv,p)
  101. int argc;
  102. char *argv[];
  103. void *p;
  104. {
  105.     register struct tcb *tcb;
  106.  
  107.     tcb = (struct tcb *)ltop(htol(argv[1]));
  108.     if(!tcpval(tcb)){
  109.         printf(Notval);
  110.         return 1;
  111.     }
  112.     tcb->srtt = atol(argv[2]);
  113.     return 0;
  114. }
  115.  
  116. /* Force a retransmission */
  117. static int
  118. dotcpkick(argc,argv,p)
  119. int argc;
  120. char *argv[];
  121. void *p;
  122. {
  123.     register struct tcb *tcb;
  124.  
  125.     tcb = (struct tcb *)ltop(htol(argv[1]));
  126.     if(kick_tcp(tcb) == -1){
  127.         printf(Notval);
  128.         return 1;
  129.     }
  130.     return 0;
  131. }
  132.  
  133. /* Set default maximum segment size */
  134. static int
  135. domss(argc,argv,p)
  136. int argc;
  137. char *argv[];
  138. void *p;
  139. {
  140.     return setshort(&Tcp_mss,"TCP MSS",argc,argv);
  141. }
  142.  
  143. /* Set default window size */
  144. static int
  145. dowindow(argc,argv,p)
  146. int argc;
  147. char *argv[];
  148. void *p;
  149. {
  150.     return setshort(&Tcp_window,"TCP window",argc,argv);
  151. }
  152.  
  153. static int
  154. dosyndata(argc,argv,p)
  155. int argc;
  156. char *argv[];
  157. void *p;
  158. {
  159.     return setbool(&Tcp_syndata,"TCP syn+data piggybacking",argc,argv);
  160. }
  161.  
  162. /* Display status of TCBs */
  163. static int
  164. dotcpstat(argc,argv,p)
  165. int argc;
  166. char *argv[];
  167. void *p;
  168. {
  169.     register struct tcb *tcb;
  170.  
  171.     if(argc < 2){
  172.         tstat();
  173.     } else {
  174.         tcb = (struct tcb *)ltop(htol(argv[1]));
  175.         if(tcpval(tcb))
  176.             st_tcp(tcb);
  177.         else
  178.             printf(Notval);
  179.     }
  180.     return 0;
  181. }
  182.  
  183. /* Dump TCP stats and summary of all TCBs
  184. /*     &TCB Rcv-Q Snd-Q  Local socket           Remote socket          State
  185.  *     1234     0     0  xxx.xxx.xxx.xxx:xxxxx  xxx.xxx.xxx.xxx:xxxxx  Established
  186.  */
  187. static int
  188. tstat()
  189. {
  190.     register int i;
  191.     register struct tcb *tcb;
  192.     int j;
  193.  
  194.     if(!Shortstatus){
  195.     for(j=i=1;i<=NUMTCPMIB;i++){
  196.         if(Tcp_mib[i].name == NULLCHAR)
  197.             continue;
  198.         printf("(%2u)%-20s%10lu",i,Tcp_mib[i].name,
  199.          Tcp_mib[i].value.integer);
  200.         if(j++ % 2)
  201.             printf("     ");
  202.         else
  203.             printf("\n");
  204.     }
  205.     if((j % 2) == 0)
  206.         printf("\n");
  207.     }
  208.  
  209.     printf("    &TCB Rcv-Q Snd-Q  Local socket           Remote socket          State\n");
  210.     for(tcb=Tcbs;tcb != NULLTCB;tcb = tcb->next){
  211.         printf("%8lx%6u%6u  ",ptol(tcb),tcb->rcvcnt,tcb->sndcnt);
  212.         printf("%-22.22s ",pinet_tcp(&tcb->conn.local));
  213.         printf("%-22.22s ",pinet_tcp(&tcb->conn.remote));
  214.         printf("%-s",Tcpstates[tcb->state]);
  215.         if(tcb->state == TCP_LISTEN && tcb->flags.clone)
  216.             printf(" (S)");
  217.         if(printf("\n") == EOF)
  218.             return 0;
  219.     }
  220.     return 0;
  221. }
  222. /* Dump a TCP control block in detail */
  223. void
  224. st_tcp(tcb)
  225. struct tcb *tcb;
  226. {
  227.     int32 sent,recvd;
  228.  
  229.     if(tcb == NULLTCB)
  230.         return;
  231.     /* Compute total data sent and received; take out SYN and FIN */
  232.     sent = tcb->snd.una - tcb->iss; /* Acknowledged data only */
  233.     recvd = tcb->rcv.nxt - tcb->irs;
  234.     switch(tcb->state){
  235.     case TCP_LISTEN:
  236.     case TCP_SYN_SENT:      /* Nothing received or acked yet */
  237.         sent = recvd = 0;
  238.         break;
  239.     case TCP_SYN_RECEIVED:
  240.         recvd--;        /* Got SYN, no data acked yet */
  241.         sent = 0;
  242.         break;
  243.     case TCP_ESTABLISHED:   /* Got and sent SYN */
  244.     case TCP_FINWAIT1:      /* FIN not acked yet */
  245.         sent--;
  246.         recvd--;
  247.         break;
  248.     case TCP_FINWAIT2:      /* Our SYN and FIN both acked */
  249.         sent -= 2;
  250.         recvd--;
  251.         break;
  252.     case TCP_CLOSE_WAIT:    /* Got SYN and FIN, our FIN not yet acked */
  253.     case TCP_CLOSING:
  254.     case TCP_LAST_ACK:
  255.         sent--;
  256.         recvd -= 2;
  257.         break;
  258.     case TCP_TIME_WAIT:     /* Sent and received SYN/FIN, all acked */
  259.         sent -= 2;
  260.         recvd -= 2;
  261.         break;
  262.     }
  263.     printf("Local: %s",pinet_tcp(&tcb->conn.local));
  264.     printf(" Remote: %s",pinet_tcp(&tcb->conn.remote));
  265.     printf(" State: %s\n",Tcpstates[tcb->state]);
  266.     printf("      Init seq    Unack     Next Resent CWind Thrsh  Wind  MSS Queue      Total\n");
  267.     printf("Send:");
  268.     printf("%9lx",tcb->iss);
  269.     printf("%9lx",tcb->snd.una);
  270.     printf("%9lx",tcb->snd.nxt);
  271.     printf("%7lu",tcb->resent);
  272.     printf("%6u",tcb->cwind);
  273.     printf("%6u",tcb->ssthresh);
  274.     printf("%6u",tcb->snd.wnd);
  275.     printf("%5u",tcb->mss);
  276.     printf("%6u",tcb->sndcnt);
  277.     printf("%11lu\n",sent);
  278.  
  279.     printf("Recv:");
  280.     printf("%9lx",tcb->irs);
  281.     printf("         ");
  282.     printf("%9lx",tcb->rcv.nxt);
  283.     printf("%7lu",tcb->rerecv);
  284.     printf("      ");
  285.     printf("      ");
  286.     printf("%6u",tcb->rcv.wnd);
  287.     printf("     ");
  288.     printf("%6u",tcb->rcvcnt);
  289.     printf("%11lu\n",recvd);
  290.  
  291.     if(tcb->reseq != (struct reseq *)NULL){
  292.         register struct reseq *rp;
  293.  
  294.         printf("Reassembly queue:\n");
  295.         for(rp = tcb->reseq;rp != (struct reseq *)NULL; rp = rp->next){
  296.             if(printf("  seq x%lx %u bytes\n",
  297.              rp->seg.seq,rp->length) == EOF)
  298.                 return;
  299.         }
  300.     }
  301.     if(tcb->backoff > 0)
  302.         printf("Backoff %u ",tcb->backoff);
  303.     if(tcb->flags.retran)
  304.         printf("Retrying ");
  305.     switch(tcb->timer.state){
  306.     case TIMER_STOP:
  307.         printf("Timer stopped ");
  308.         break;
  309.     case TIMER_RUN:
  310.         printf("Timer running (%ld/%ld ms) ",
  311.          (long)read_timer(&tcb->timer),
  312.          (long)dur_timer(&tcb->timer));
  313.         break;
  314.     case TIMER_EXPIRE:
  315.         printf("Timer expired ");
  316.     }
  317.     printf("SRTT %ld ms Mean dev %ld ms\n",tcb->srtt,tcb->mdev);
  318. }
  319.